package com.ssy.lingxi.member.merchant.serviceimpl.base;

import com.ssy.lingxi.common.constant.basic.EnableDisableStatus;
import com.ssy.lingxi.common.constant.member.MemberConfigTagEnum;
import com.ssy.lingxi.common.exception.BusinessException;
import com.ssy.lingxi.common.response.ResponseCode;
import com.ssy.lingxi.common.response.Wrapper;
import com.ssy.lingxi.member.merchant.api.constant.MemberConfigFieldTypeEnum;
import com.ssy.lingxi.member.merchant.api.constant.MemberRelationTypeEnum;
import com.ssy.lingxi.member.merchant.entity.*;
import com.ssy.lingxi.member.merchant.model.bo.DetailCheckBO;
import com.ssy.lingxi.member.merchant.model.bo.DetailValueBO;
import com.ssy.lingxi.member.merchant.model.bo.MemberDetailLabelBO;
import com.ssy.lingxi.member.merchant.model.bo.WorkflowTaskResultBO;
import com.ssy.lingxi.member.merchant.model.constant.*;
import com.ssy.lingxi.member.merchant.model.vo.basic.response.*;
import com.ssy.lingxi.member.merchant.repository.*;
import com.ssy.lingxi.member.merchant.service.base.IBaseMemberRegisterDetailService;
import com.ssy.lingxi.member.merchant.service.feign.IPlatformTemplateFeignService;
import com.ssy.lingxi.member.merchant.service.feign.IWorkflowFeignService;
import com.ssy.lingxi.member.merchant.utils.NumberUtil;
import com.ssy.lingxi.member.merchant.utils.SecurityStringUtils;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.transaction.interceptor.TransactionAspectSupport;
import org.springframework.util.CollectionUtils;
import org.springframework.util.StringUtils;

import javax.annotation.Resource;
import java.util.*;
import java.util.stream.Collectors;
import java.util.stream.Stream;

/**
 * 会员注册信息查询相关接口实现类
 *
 * @author 万宁
 * @version 2.0.0
 * @date 2021-01-14
 */
@Service
public class BaseMemberRegisterDetailServiceImpl implements IBaseMemberRegisterDetailService {
    @Resource
    private MemberRepository memberRepository;

    @Resource
    private MemberRelationRepository relationRepository;

    @Resource
    private MemberRegisterDetailRepository memberRegisterDetailRepository;

    @Resource
    private MemberUserRepository memberUserRepository;

    @Resource
    private CountryAreaRepository countryAreaRepository;

    @Resource
    private IWorkflowFeignService workflowFeignService;

    @Resource
    private IPlatformTemplateFeignService platformTemplateFeignService;

    /**
     * 将会员注册资料转换为前端注册页面、新增会员页面内容
     *
     * @param memberConfigs 会员注册资料
     * @return 转换结果
     */
    @Override
    public List<MemberConfigGroupVO> groupMemberConfig(List<MemberConfigDO> memberConfigs) {
        if (CollectionUtils.isEmpty(memberConfigs)) {
            return new ArrayList<>();
        }

        //筛选出状态为 “启用” 的配置，按照groupName进行分组
        Map<String, List<MemberConfigDO>> groupList = memberConfigs.stream().filter(c -> c.getFieldStatus().equals(MemberConfigStatusEnum.ENABLED.getCode()))
                .collect(Collectors.groupingBy(MemberConfigDO::getGroupName));

        return groupList.entrySet().stream().map(e -> {
            MemberConfigGroupVO configGroup = new MemberConfigGroupVO();
            configGroup.setGroupName(e.getKey());

            List<ConfigDetailVO> elements = e.getValue().stream().map(c -> {
                ConfigDetailVO detail = new ConfigDetailVO();
                detail.setId(c.getId());
                detail.setFieldName(c.getFieldName());
                detail.setFieldLocalName(c.getFieldLocalName());
                detail.setFieldType(c.getFieldType());
                detail.setAttr(c.getAttr());
                detail.setFieldEmpty(c.getFieldEmpty());
                detail.setFieldLength(c.getFieldLength());
                detail.setFieldOrder(c.getFieldOrder());
                detail.setFieldRemark(c.getFieldRemark());
                detail.setRuleEnum(c.getRuleEnum());
                detail.setPattern(c.getRuleEnum().equals(0) ? "" : MemberConfigCheckRuleEnum.getJsPattern(c.getRuleEnum()));
                detail.setMsg(c.getRuleEnum().equals(0) ? "" : MemberConfigCheckRuleEnum.getMsg(c.getRuleEnum()));
                detail.setFieldEnum(CollectionUtils.isEmpty(c.getLabels()) ? new ArrayList<>() : c.getLabels().stream().sorted(Comparator.comparingInt(MemberConfigLabelDO::getLabelOrder)).map(label -> new ConfigDetailLabelVO(label.getId(), label.getLabelValue())).collect(Collectors.toList()));
                return detail;
            }).sorted(Comparator.comparingInt(ConfigDetailVO::getFieldOrder)).collect(Collectors.toList());

            configGroup.setElements(elements);
            return configGroup;
        }).sorted(Comparator.comparingInt(a -> a.getElements().get(0).getFieldOrder())).collect(Collectors.toList());
    }

    /**
     * 会员注册时，校验注册资料，并返回会员名称
     *
     * @param detailMap          注册资料
     * @param memberConfigList   角色关联的会员注册资料配置
     * @param registerDetailList 返回的注册资料，其版本为“待审核”
     * @param defaultName              如果注册资料为空，用手机号作为公司名称
     * @return 校验结果
     */
    @Override
    public Wrapper<String> checkMemberRegisterDetail(Map<String, Object> detailMap, List<MemberConfigDO> memberConfigList, List<MemberRegisterDetailDO> registerDetailList, String defaultName) {
        if(CollectionUtils.isEmpty(memberConfigList)) {
            return Wrapper.success(defaultName);
        }

        if(CollectionUtils.isEmpty(detailMap)) {
            return Wrapper.fail(ResponseCode.MC_MC_MEMBER_DETAIL_CAN_NOT_BE_EMPTY);
        }

        String memberName = "";
        for (Map.Entry<String, Object> entry : detailMap.entrySet()) {
            String key = entry.getKey();
            String value = entry.getValue() instanceof HashMap ? SecurityStringUtils.serializeObject(entry.getValue()) : String.valueOf(entry.getValue());

            MemberConfigDO configDO = memberConfigList.stream().filter(c -> c.getFieldName().equals(key)).findFirst().orElse(null);
            if (configDO == null) {
                return Wrapper.fail(ResponseCode.MC_MS_MEMBER_DETAIL_FIELD_DOES_NOT_EXIST);
            }

            Wrapper<DetailCheckBO> checkResult = checkDetail(configDO, value);
            if(checkResult.getCode() != ResponseCode.SUCCESS.getCode()) {
                return Wrapper.fail(checkResult.getCode(), checkResult.getMessage());
            }

            if(checkResult.getData().getTagEnum().equals(MemberConfigTagEnum.Member_Name.getCode())) {
                memberName = checkResult.getData().getMemberName();
            }

            MemberRegisterDetailDO memberRegisterDetailDO = new MemberRegisterDetailDO();
            memberRegisterDetailDO.setMemberConfig(configDO);
            memberRegisterDetailDO.setGroupName(configDO.getGroupName());
            //版本
            memberRegisterDetailDO.setVersion(MemberDetailVersionEnum.TO_BE_VALIDATE.getCode());
            memberRegisterDetailDO.setFieldName(configDO.getFieldName());
            memberRegisterDetailDO.setFieldLocalName(configDO.getFieldLocalName());
            memberRegisterDetailDO.setFieldType(configDO.getFieldType());
            memberRegisterDetailDO.setAttr(configDO.getAttr());
            memberRegisterDetailDO.setTagEnum(configDO.getTagEnum());
            memberRegisterDetailDO.setStatus(configDO.getFieldStatus());
            memberRegisterDetailDO.setValidate(configDO.getValidate());
            memberRegisterDetailDO.setDetail(checkResult.getData().getDetail());
            memberRegisterDetailDO.setProvinceCode(checkResult.getData().getProvinceCode());
            memberRegisterDetailDO.setProvinceName(checkResult.getData().getProvinceName());
            memberRegisterDetailDO.setCityCode(checkResult.getData().getCityCode());
            memberRegisterDetailDO.setCityName(checkResult.getData().getCityName());
            memberRegisterDetailDO.setDistrictCode(checkResult.getData().getDistrictCode());
            memberRegisterDetailDO.setDistrictName(checkResult.getData().getDistrictName());
            memberRegisterDetailDO.setLabels(checkResult.getData().getLabels());
            registerDetailList.add(memberRegisterDetailDO);
        }

        return Wrapper.success(StringUtils.hasLength(memberName) ? memberName : defaultName);
    }

    /**
     * 比较两个版本的注册资料，是否有修改
     *
     * @param member            会员
     * @param toValidateDetails 新增的注册资料
     * @return 是否有修改
     */
    @Override
    public boolean isDetailModified(MemberDO member, List<MemberRegisterDetailDO> toValidateDetails) {
        List<MemberRegisterDetailDO> usingDetails = memberRegisterDetailRepository.findByMemberAndVersion(member, MemberDetailVersionEnum.USING.getCode());
        if(CollectionUtils.isEmpty(usingDetails) && CollectionUtils.isEmpty(toValidateDetails)) {
            return false;
        }

        if(CollectionUtils.isEmpty(usingDetails) && !CollectionUtils.isEmpty(toValidateDetails)) {
            return true;
        }

        if(!CollectionUtils.isEmpty(usingDetails) && CollectionUtils.isEmpty(toValidateDetails)) {
            return true;
        }

        if(usingDetails.size() != toValidateDetails.size()) {
            return true;
        }

        //比较字段、值
        return toValidateDetails.stream().anyMatch(toValidateDetail -> usingDetails.stream().noneMatch(usingDetail -> usingDetail.getFieldName().equals(toValidateDetail.getFieldName()) && usingDetail.getDetail().equals(toValidateDetail.getDetail())));
    }

    /**
     * 查询会员注册资料
     *
     * @param member      会员
     * @param versionEnum 注册资料版本
     * @return 查询结果
     */
    @Override
    public List<RegisterDetailGroupVO> groupMemberRegisterDetail(MemberDO member, MemberDetailVersionEnum versionEnum) {
        List<MemberRegisterDetailDO> registerDetails = memberRegisterDetailRepository.findByMemberAndVersion(member, versionEnum.getCode());
        if (CollectionUtils.isEmpty(registerDetails)) {
            return new ArrayList<>();
        }

        //筛选出状态为 “启用” 的配置，按照groupName进行分组
        Map<String, List<MemberRegisterDetailDO>> groupList = registerDetails.stream().filter(c -> c.getStatus().equals(MemberConfigStatusEnum.ENABLED.getCode()))
                .collect(Collectors.groupingBy(MemberRegisterDetailDO::getGroupName));

        return groupList.entrySet().stream().map(e -> {
            RegisterDetailGroupVO detailGroup = new RegisterDetailGroupVO();
            detailGroup.setGroupName(e.getKey());

            List<RegisterDetailVO> elements = e.getValue().stream().map(c -> {
                RegisterDetailVO detail = new RegisterDetailVO();
                detail.setFieldName(c.getFieldName());
                detail.setFieldLocalName(c.getFieldLocalName());
                detail.setFieldType(c.getFieldType());
                detail.setAttr(c.getAttr());
                detail.setFieldEmpty(c.getMemberConfig().getFieldEmpty());
                detail.setFieldLength(c.getMemberConfig().getFieldLength());
                detail.setFieldOrder(c.getMemberConfig().getFieldOrder());
                detail.setFieldRemark(c.getMemberConfig().getFieldRemark());
                detail.setRuleEnum(c.getMemberConfig().getRuleEnum());
                detail.setPattern(c.getMemberConfig().getRuleEnum().equals(0) ? "" : MemberConfigCheckRuleEnum.getJsPattern(c.getMemberConfig().getRuleEnum()));
                detail.setMsg(c.getMemberConfig().getRuleEnum().equals(0) ? "" : MemberConfigCheckRuleEnum.getMsg(c.getMemberConfig().getRuleEnum()));
                detail.setFieldEnum(CollectionUtils.isEmpty(c.getMemberConfig().getLabels()) ? new ArrayList<>() : c.getMemberConfig().getLabels().stream().sorted(Comparator.comparingInt(MemberConfigLabelDO::getLabelOrder)).map(label -> new ConfigDetailLabelVO(label.getId(), label.getLabelValue())).collect(Collectors.toList()));

                DetailValueBO valueBO = getDetailValue(c);
                detail.setFieldValue(valueBO.getFieldValue());
                detail.setLastValue(valueBO.getLastValue());

                return detail;
            }).sorted(Comparator.comparingInt(RegisterDetailVO::getFieldOrder)).collect(Collectors.toList());

            detailGroup.setElements(elements);
            return detailGroup;
        }).sorted(Comparator.comparingInt(a -> a.getElements().get(0).getFieldOrder())).collect(Collectors.toList());
    }

    /**
     * 查询会员注册资料（Using版本优先，如无则查询正在审核的版本）
     *
     * @param member 会员
     * @return 查询结果
     */
    @Override
    public List<RegisterDetailGroupVO> switchMemberRegisterDetail(MemberDO member) {
        List<MemberRegisterDetailDO> registerDetailList = memberRegisterDetailRepository.findByMember(member);
        if (CollectionUtils.isEmpty(registerDetailList)) {
            return new ArrayList<>();
        }

        List<MemberRegisterDetailDO> registerDetails = registerDetailList.stream().filter(registerDetail -> registerDetail.getVersion().equals(MemberDetailVersionEnum.USING.getCode())).collect(Collectors.toList());
        if(CollectionUtils.isEmpty(registerDetails)) {
            registerDetails = registerDetailList.stream().filter(registerDetail -> registerDetail.getVersion().equals(MemberDetailVersionEnum.TO_BE_VALIDATE.getCode())).collect(Collectors.toList());
        }

        //筛选出状态为 “启用” 的配置，按照groupName进行分组
        Map<String, List<MemberRegisterDetailDO>> groupList = registerDetails.stream().filter(c -> c.getStatus().equals(MemberConfigStatusEnum.ENABLED.getCode()))
                .collect(Collectors.groupingBy(MemberRegisterDetailDO::getGroupName));

        return groupList.entrySet().stream().map(e -> {
            RegisterDetailGroupVO detailGroup = new RegisterDetailGroupVO();
            detailGroup.setGroupName(e.getKey());

            List<RegisterDetailVO> elements = e.getValue().stream().map(c -> {
                RegisterDetailVO detail = new RegisterDetailVO();
                detail.setFieldName(c.getFieldName());
                detail.setFieldLocalName(c.getFieldLocalName());
                detail.setFieldType(c.getFieldType());
                detail.setAttr(c.getAttr());
                detail.setFieldEmpty(c.getMemberConfig().getFieldEmpty());
                detail.setFieldLength(c.getMemberConfig().getFieldLength());
                detail.setFieldOrder(c.getMemberConfig().getFieldOrder());
                detail.setFieldRemark(c.getMemberConfig().getFieldRemark());
                detail.setRuleEnum(c.getMemberConfig().getRuleEnum());
                detail.setPattern(c.getMemberConfig().getRuleEnum().equals(0) ? "" : MemberConfigCheckRuleEnum.getJsPattern(c.getMemberConfig().getRuleEnum()));
                detail.setMsg(c.getMemberConfig().getRuleEnum().equals(0) ? "" : MemberConfigCheckRuleEnum.getMsg(c.getMemberConfig().getRuleEnum()));
                detail.setFieldEnum(CollectionUtils.isEmpty(c.getMemberConfig().getLabels()) ? new ArrayList<>() : c.getMemberConfig().getLabels().stream().sorted(Comparator.comparingInt(MemberConfigLabelDO::getLabelOrder)).map(label -> new ConfigDetailLabelVO(label.getId(), label.getLabelValue())).collect(Collectors.toList()));

                DetailValueBO valueBO = getDetailValue(c);
                detail.setFieldValue(valueBO.getFieldValue());
                detail.setLastValue(valueBO.getLastValue());

                return detail;
            }).sorted(Comparator.comparingInt(RegisterDetailVO::getFieldOrder)).collect(Collectors.toList());

            detailGroup.setElements(elements);
            return detailGroup;
        }).sorted(Comparator.comparingInt(a -> a.getElements().get(0).getFieldOrder())).collect(Collectors.toList());
    }

    /**
     * 查询会员注册资料（两个版本合并）
     *
     * @param member 会员
     * @return 查询结果
     */
    @Override
    public List<RegisterDetailGroupVO> groupMemberRegisterDetail(MemberDO member) {
        List<MemberRegisterDetailDO> registerDetails = memberRegisterDetailRepository.findByMember(member);
        if (CollectionUtils.isEmpty(registerDetails)) {
            return new ArrayList<>();
        }

        List<MemberRegisterDetailDO> usingList = registerDetails.stream().filter(registerDetail -> registerDetail.getVersion().equals(MemberDetailVersionEnum.USING.getCode())).collect(Collectors.toList());
        List<MemberRegisterDetailDO> validateList = registerDetails.stream().filter(registerDetail -> registerDetail.getVersion().equals(MemberDetailVersionEnum.TO_BE_VALIDATE.getCode())).collect(Collectors.toList());

        if(CollectionUtils.isEmpty(validateList)) {
            //正在使用的版本
            Map<String, List<MemberRegisterDetailDO>> groupList = usingList.stream().filter(c -> c.getStatus().equals(MemberConfigStatusEnum.ENABLED.getCode()))
                    .collect(Collectors.groupingBy(MemberRegisterDetailDO::getGroupName));

            return groupList.entrySet().stream().map(e -> {
                RegisterDetailGroupVO detailGroup = new RegisterDetailGroupVO();
                detailGroup.setGroupName(e.getKey());

                List<RegisterDetailVO> elements = e.getValue().stream().map(c -> {
                    RegisterDetailVO detail = new RegisterDetailVO();
                    detail.setFieldName(c.getFieldName());
                    detail.setFieldLocalName(c.getFieldLocalName());
                    detail.setFieldType(c.getFieldType());
                    detail.setAttr(c.getAttr());
                    detail.setFieldEmpty(c.getMemberConfig().getFieldEmpty());
                    detail.setFieldLength(c.getMemberConfig().getFieldLength());
                    detail.setFieldOrder(c.getMemberConfig().getFieldOrder());
                    detail.setFieldRemark(c.getMemberConfig().getFieldRemark());
                    detail.setRuleEnum(c.getMemberConfig().getRuleEnum());
                    detail.setPattern(c.getMemberConfig().getRuleEnum().equals(0) ? "" : MemberConfigCheckRuleEnum.getJsPattern(c.getMemberConfig().getRuleEnum()));
                    detail.setMsg(c.getMemberConfig().getRuleEnum().equals(0) ? "" : MemberConfigCheckRuleEnum.getMsg(c.getMemberConfig().getRuleEnum()));
                    detail.setFieldEnum(CollectionUtils.isEmpty(c.getMemberConfig().getLabels()) ? new ArrayList<>() : c.getMemberConfig().getLabels().stream().sorted(Comparator.comparingInt(MemberConfigLabelDO::getLabelOrder)).map(label -> new ConfigDetailLabelVO(label.getId(), label.getLabelValue())).collect(Collectors.toList()));

                    DetailValueBO valueBO = getDetailValue(c);
                    detail.setFieldValue(valueBO.getFieldValue());
                    detail.setLastValue(valueBO.getLastValue());

                    return detail;
                }).sorted(Comparator.comparingInt(RegisterDetailVO::getFieldOrder)).collect(Collectors.toList());

                detailGroup.setElements(elements);
                return detailGroup;
            }).sorted(Comparator.comparingInt(a -> a.getElements().get(0).getFieldOrder())).collect(Collectors.toList());
        } else {
            //待审核的版本
            Map<String, List<MemberRegisterDetailDO>> groupList = validateList.stream().filter(c -> c.getStatus().equals(MemberConfigStatusEnum.ENABLED.getCode()))
                    .collect(Collectors.groupingBy(MemberRegisterDetailDO::getGroupName));

            return groupList.entrySet().stream().map(e -> {
                RegisterDetailGroupVO detailGroup = new RegisterDetailGroupVO();
                detailGroup.setGroupName(e.getKey());

                List<RegisterDetailVO> elements = e.getValue().stream().map(c -> {
                    MemberRegisterDetailDO usingDetail = usingList.stream().filter(u -> u.getFieldName().equals(c.getFieldName())).findFirst().orElse(null);

                    RegisterDetailVO detail = new RegisterDetailVO();
                    detail.setFieldName(c.getFieldName());
                    detail.setFieldLocalName(c.getFieldLocalName());
                    detail.setFieldType(c.getFieldType());
                    detail.setAttr(c.getAttr());
                    detail.setFieldEmpty(c.getMemberConfig().getFieldEmpty());
                    detail.setFieldLength(c.getMemberConfig().getFieldLength());
                    detail.setFieldOrder(c.getMemberConfig().getFieldOrder());
                    detail.setFieldRemark(c.getMemberConfig().getFieldRemark());
                    detail.setRuleEnum(c.getMemberConfig().getRuleEnum());
                    detail.setPattern(c.getMemberConfig().getRuleEnum().equals(0) ? "" : MemberConfigCheckRuleEnum.getJsPattern(c.getMemberConfig().getRuleEnum()));
                    detail.setMsg(c.getMemberConfig().getRuleEnum().equals(0) ? "" : MemberConfigCheckRuleEnum.getMsg(c.getMemberConfig().getRuleEnum()));
                    detail.setFieldEnum(CollectionUtils.isEmpty(c.getMemberConfig().getLabels()) ? new ArrayList<>() : c.getMemberConfig().getLabels().stream().sorted(Comparator.comparingInt(MemberConfigLabelDO::getLabelOrder)).map(label -> new ConfigDetailLabelVO(label.getId(), label.getLabelValue())).collect(Collectors.toList()));
                    if(usingDetail == null) {
                        DetailValueBO valueBO = getDetailValue(c);
                        detail.setFieldValue(valueBO.getFieldValue());
                        detail.setLastValue(valueBO.getLastValue());
                    } else {
                        detail.setFieldValue(getSingleDetailValue(c));
                        detail.setLastValue(getSingleDetailValue(usingDetail));
                    }

                    return detail;
                }).sorted(Comparator.comparingInt(RegisterDetailVO::getFieldOrder)).collect(Collectors.toList());

                detailGroup.setElements(elements);
                return detailGroup;
            }).sorted(Comparator.comparingInt(a -> a.getElements().get(0).getFieldOrder())).collect(Collectors.toList());
        }

    }

    /**
     * 查询会员注册资料（查询指定版本）
     *
     * @param member      会员
     * @param versionEnum 指定版本
     * @return 查询结果
     */
    @Override
    public List<DetailTextGroupVO> groupMemberRegisterDetailText(MemberDO member, MemberDetailVersionEnum versionEnum) {
        List<MemberRegisterDetailDO> registerDetails = memberRegisterDetailRepository.findByMemberAndVersion(member, versionEnum.getCode());
        if (CollectionUtils.isEmpty(registerDetails)) {
            return new ArrayList<>();
        }

        //筛选出状态为 “启用” 的配置，按照groupName进行分组
        Map<String, List<MemberRegisterDetailDO>> groupList = registerDetails.stream().filter(c -> c.getStatus().equals(MemberConfigStatusEnum.ENABLED.getCode()))
                .collect(Collectors.groupingBy(MemberRegisterDetailDO::getGroupName));

        return groupList.entrySet().stream().map(e -> {
            DetailTextGroupVO detailGroup = new DetailTextGroupVO();
            detailGroup.setGroupName(e.getKey());

            List<DetailTextVO> elements = e.getValue().stream().map(c -> {
                DetailTextVO detail = new DetailTextVO();
                detail.setFieldType(c.getFieldType());
                detail.setFieldLocalName(c.getFieldLocalName());
                detail.setFieldOrder(c.getMemberConfig().getFieldOrder());
                detail.setFieldValue(c.getDetail());
                detail.setLastValue("");
                return detail;
            }).sorted(Comparator.comparingInt(DetailTextVO::getFieldOrder)).collect(Collectors.toList());

            detailGroup.setElements(elements);
            return detailGroup;
        }).sorted(Comparator.comparingInt(a -> a.getElements().get(0).getFieldOrder())).collect(Collectors.toList());
    }

    /**
     * 查询会员注册资料（Using版本优先，如果没有则查询正在审核的版本）
     *
     * @param member 会员
     * @return 查询结果
     */
    @Override
    public List<DetailTextGroupVO> switchMemberRegisterDetailText(MemberDO member) {
        List<MemberRegisterDetailDO> registerDetailList = memberRegisterDetailRepository.findByMember(member);
        if (CollectionUtils.isEmpty(registerDetailList)) {
            return new ArrayList<>();
        }

        List<MemberRegisterDetailDO> registerDetails = registerDetailList.stream().filter(registerDetail -> registerDetail.getVersion().equals(MemberDetailVersionEnum.USING.getCode())).collect(Collectors.toList());
        if(CollectionUtils.isEmpty(registerDetails)) {
            registerDetails = registerDetailList.stream().filter(registerDetail -> registerDetail.getVersion().equals(MemberDetailVersionEnum.TO_BE_VALIDATE.getCode())).collect(Collectors.toList());
        }

        //筛选出状态为 “启用” 的配置，按照groupName进行分组
        Map<String, List<MemberRegisterDetailDO>> groupList = registerDetails.stream().filter(c -> c.getStatus().equals(MemberConfigStatusEnum.ENABLED.getCode()))
                .collect(Collectors.groupingBy(MemberRegisterDetailDO::getGroupName));

        return groupList.entrySet().stream().map(e -> {
            DetailTextGroupVO detailGroup = new DetailTextGroupVO();
            detailGroup.setGroupName(e.getKey());

            List<DetailTextVO> elements = e.getValue().stream().map(c -> {
                DetailTextVO detail = new DetailTextVO();
                detail.setFieldType(c.getFieldType());
                detail.setFieldLocalName(c.getFieldLocalName());
                detail.setFieldOrder(c.getMemberConfig().getFieldOrder());
                detail.setFieldValue(c.getDetail());
                detail.setLastValue("");
                return detail;
            }).sorted(Comparator.comparingInt(DetailTextVO::getFieldOrder)).collect(Collectors.toList());

            detailGroup.setElements(elements);
            return detailGroup;
        }).sorted(Comparator.comparingInt(a -> a.getElements().get(0).getFieldOrder())).collect(Collectors.toList());
    }

    /**
     * 查询会员注册资料（文本显示，两个版本合并）
     *
     * @param member 会议
     * @return 查询结果
     */
    @Override
    public List<DetailTextGroupVO> groupMemberRegisterDetailText(MemberDO member) {
        List<MemberRegisterDetailDO> registerDetails = memberRegisterDetailRepository.findByMember(member);
        if (CollectionUtils.isEmpty(registerDetails)) {
            return new ArrayList<>();
        }

        List<MemberRegisterDetailDO> validateList = registerDetails.stream().filter(registerDetail -> registerDetail.getVersion().equals(MemberDetailVersionEnum.TO_BE_VALIDATE.getCode())).collect(Collectors.toList());

        List<MemberRegisterDetailDO> usingList = registerDetails.stream().filter(registerDetail -> registerDetail.getVersion().equals(MemberDetailVersionEnum.USING.getCode())).collect(Collectors.toList());

        if(CollectionUtils.isEmpty(validateList)) {
            //筛选出状态为 “启用” 的配置，按照groupName进行分组
            Map<String, List<MemberRegisterDetailDO>> groupList = usingList.stream().filter(c -> c.getStatus().equals(MemberConfigStatusEnum.ENABLED.getCode()))
                    .collect(Collectors.groupingBy(MemberRegisterDetailDO::getGroupName));

            return groupList.entrySet().stream().map(e -> {
                DetailTextGroupVO detailGroup = new DetailTextGroupVO();
                detailGroup.setGroupName(e.getKey());

                List<DetailTextVO> elements = e.getValue().stream().map(c -> {
                    DetailTextVO detail = new DetailTextVO();
                    detail.setFieldType(c.getFieldType());
                    detail.setFieldLocalName(c.getFieldLocalName());
                    detail.setFieldOrder(c.getMemberConfig().getFieldOrder());
                    detail.setFieldValue(c.getDetail());
                    detail.setLastValue("");
                    return detail;
                }).sorted(Comparator.comparingInt(DetailTextVO::getFieldOrder)).collect(Collectors.toList());

                detailGroup.setElements(elements);
                return detailGroup;
            }).sorted(Comparator.comparingInt(a -> a.getElements().get(0).getFieldOrder())).collect(Collectors.toList());
        } else {
            Map<String, List<MemberRegisterDetailDO>> groupList = validateList.stream().filter(c -> c.getStatus().equals(MemberConfigStatusEnum.ENABLED.getCode()))
                    .collect(Collectors.groupingBy(MemberRegisterDetailDO::getGroupName));

            return groupList.entrySet().stream().map(e -> {
                DetailTextGroupVO detailGroup = new DetailTextGroupVO();
                detailGroup.setGroupName(e.getKey());

                List<DetailTextVO> elements = e.getValue().stream().map(c -> {
                    DetailTextVO detail = new DetailTextVO();
                    detail.setFieldType(c.getFieldType());
                    detail.setFieldLocalName(c.getFieldLocalName());
                    detail.setFieldOrder(c.getMemberConfig().getFieldOrder());
                    detail.setFieldValue(c.getDetail());

                    MemberRegisterDetailDO usingDetail = usingList.stream().filter(u -> u.getFieldName().equals(c.getFieldName())).findFirst().orElse(null);
                    detail.setLastValue(usingDetail == null ? "" : usingDetail.getDetail());
                    return detail;
                }).sorted(Comparator.comparingInt(DetailTextVO::getFieldOrder)).collect(Collectors.toList());

                detailGroup.setElements(elements);
                return detailGroup;
            }).sorted(Comparator.comparingInt(a -> a.getElements().get(0).getFieldOrder())).collect(Collectors.toList());
        }
    }

    /**
     * 新增角色时，合并现有的注册资料与新增角色的注册资料
     *
     * @param member      会员
     * @param versionEnum 注册资料的版本
     * @param roleDO      新增的角色
     * @return 合并结果
     */
    @Override
    public List<RegisterDetailGroupVO> mergeMemberRegisterDetail(MemberDO member, MemberDetailVersionEnum versionEnum, RoleDO roleDO) {
        List<MemberConfigDO> memberConfigs = new ArrayList<>(roleDO.getConfigs());
        if (CollectionUtils.isEmpty(memberConfigs)) {
            return groupMemberRegisterDetail(member, versionEnum);
        }

        List<MemberRegisterDetailDO> registerDetails = memberRegisterDetailRepository.findByMemberAndVersion(member, versionEnum.getCode());

        List<MemberRegisterDetailDO> plusList = memberConfigs.stream().filter(memberConfig -> registerDetails.stream().noneMatch(registerDetail -> registerDetail.getMemberConfig().getId().equals(memberConfig.getId()))).map(memberConfig -> {
            MemberRegisterDetailDO detailDO = new MemberRegisterDetailDO();
            detailDO.setGroupName(memberConfig.getGroupName());
            detailDO.setMemberConfig(memberConfig);
            detailDO.setFieldType(memberConfig.getFieldType());
            detailDO.setFieldName(memberConfig.getFieldName());
            detailDO.setFieldLocalName(memberConfig.getFieldLocalName());
            detailDO.setAttr(memberConfig.getAttr());
            detailDO.setDetail("");
            detailDO.setProvinceCode("");
            detailDO.setCityCode("");
            detailDO.setDistrictCode("");
            detailDO.setLabels(new ArrayList<>());
            detailDO.setStatus(EnableDisableStatus.ENABLE.getCode());
            return detailDO;
        }).collect(Collectors.toList());

        if (CollectionUtils.isEmpty(plusList)) {
            return groupMemberRegisterDetail(member, versionEnum);
        }

        registerDetails.addAll(plusList);

        //筛选出状态为 “启用” 的配置，按照groupName进行分组
        Map<String, List<MemberRegisterDetailDO>> groupList = registerDetails.stream().filter(c -> c.getStatus().equals(MemberConfigStatusEnum.ENABLED.getCode()))
                .collect(Collectors.groupingBy(MemberRegisterDetailDO::getGroupName));

        return groupList.entrySet().stream().map(e -> {
            RegisterDetailGroupVO detailGroup = new RegisterDetailGroupVO();
            detailGroup.setGroupName(e.getKey());

            List<RegisterDetailVO> elements = e.getValue().stream().map(c -> {
                RegisterDetailVO detail = new RegisterDetailVO();
                detail.setFieldName(c.getFieldName());
                detail.setFieldLocalName(c.getFieldLocalName());
                detail.setFieldType(c.getFieldType());
                detail.setAttr(c.getAttr());
                detail.setFieldEmpty(c.getMemberConfig().getFieldEmpty());
                detail.setFieldLength(c.getMemberConfig().getFieldLength());
                detail.setFieldOrder(c.getMemberConfig().getFieldOrder());
                detail.setFieldRemark(c.getMemberConfig().getFieldRemark());
                detail.setRuleEnum(c.getMemberConfig().getRuleEnum());
                detail.setPattern(c.getMemberConfig().getRuleEnum().equals(0) ? "" : MemberConfigCheckRuleEnum.getJsPattern(c.getMemberConfig().getRuleEnum()));
                detail.setMsg(c.getMemberConfig().getRuleEnum().equals(0) ? "" : MemberConfigCheckRuleEnum.getMsg(c.getMemberConfig().getRuleEnum()));
                detail.setFieldEnum(CollectionUtils.isEmpty(c.getMemberConfig().getLabels()) ? new ArrayList<>() : c.getMemberConfig().getLabels().stream().sorted(Comparator.comparingInt(MemberConfigLabelDO::getLabelOrder)).map(label -> new ConfigDetailLabelVO(label.getId(), label.getLabelValue())).collect(Collectors.toList()));

                DetailValueBO valueBO = getDetailValue(c);
                detail.setFieldValue(valueBO.getFieldValue());
                detail.setLastValue(valueBO.getLastValue());

                return detail;
            }).sorted(Comparator.comparingInt(RegisterDetailVO::getFieldOrder)).collect(Collectors.toList());

            detailGroup.setElements(elements);
            return detailGroup;
        }).sorted(Comparator.comparingInt(a -> a.getElements().get(0).getFieldOrder())).collect(Collectors.toList());
    }

    /**
     * 会员审核通过后（将注册资料的版本更新为正在使用的版本
     *
     * @param member 会员
     */
    @Transactional(rollbackFor = BusinessException.class)
    @Override
    public void updateMemberRegisterDetailToUsing(MemberDO member) {
        Set<MemberRegisterDetailDO> registerDetails = member.getRegisterDetails();
        if (CollectionUtils.isEmpty(registerDetails)) {
            return;
        }

        //删除正在使用的版本
        List<MemberRegisterDetailDO> deleteList = registerDetails.stream().filter(registerDetail -> registerDetail.getVersion().equals(MemberDetailVersionEnum.USING.getCode())).collect(Collectors.toList());
        memberRegisterDetailRepository.deleteAll(deleteList);

        List<MemberRegisterDetailDO> updateList = registerDetails.stream().filter(registerDetail -> registerDetail.getVersion().equals(MemberDetailVersionEnum.TO_BE_VALIDATE.getCode())).collect(Collectors.toList());
        updateList.forEach(registerDetail -> registerDetail.setVersion(MemberDetailVersionEnum.USING.getCode()));
        memberRegisterDetailRepository.saveAll(updateList);
    }


    /**
     * 查询会员标签注册资料
     *
     * @param memberId 会员Id
     * @return 查询结果
     */
    @Override
    public Wrapper<MemberRegisterTagVO> getMemberRegisterTagDetail(Long memberId) {
        MemberDO memberDO = memberRepository.findById(memberId).orElse(null);
        if (memberDO == null) {
            return Wrapper.fail(ResponseCode.MC_MS_MEMBER_DOES_NOT_EXIST);
        }

        return getMemberRegisterTagDetail(memberDO);
    }

    /**
     * 查询会员标签注册资料
     *
     * @param member 会员
     * @return 查询结果
     */
    @Override
    public Wrapper<MemberRegisterTagVO> getMemberRegisterTagDetail(MemberDO member) {
        List<MemberRegisterDetailDO> registerDetails = memberRegisterDetailRepository.findByMemberAndVersion(member, MemberDetailVersionEnum.USING.getCode());

        MemberRegisterTagVO queryVO = new MemberRegisterTagVO();
        queryVO.setMemberId(member.getId());
        queryVO.setName(member.getName());
        queryVO.setPhone(member.getPhone());
        queryVO.setLogo(member.getLogo());

        if (!CollectionUtils.isEmpty(registerDetails)) {
            for (MemberRegisterDetailDO detail : registerDetails) {
                if (detail.getTagEnum().equals(MemberConfigTagEnum.Member_Identity_Card.getCode())) {
                    queryVO.setIdentityCard(detail.getDetail());
                } else if (detail.getTagEnum().equals(MemberConfigTagEnum.Member_Identity_Card_Front.getCode())) {
                    queryVO.setIdentityCardFront(detail.getDetail());
                } else if (detail.getTagEnum().equals(MemberConfigTagEnum.Member_Identity_Card_Back.getCode())) {
                    queryVO.setIdentityCardBack(detail.getDetail());
                } else if (detail.getTagEnum().equals(MemberConfigTagEnum.Legal_Person_Name.getCode())) {
                    queryVO.setLegalPersonName(detail.getDetail());
                } else if (detail.getTagEnum().equals(MemberConfigTagEnum.Legal_Person_Phone.getCode())) {
                    queryVO.setLegalPersonPhone(detail.getDetail());
                } else if (detail.getTagEnum().equals(MemberConfigTagEnum.Legal_Person_Identity_Card.getCode())) {
                    queryVO.setLegalPersonIdentityCard(detail.getDetail());
                } else if (detail.getTagEnum().equals(MemberConfigTagEnum.Legal_Person_Identity_Card_Front.getCode())) {
                    queryVO.setLegalPersonIdentityCardFront(detail.getDetail());
                } else if (detail.getTagEnum().equals(MemberConfigTagEnum.Legal_Person_Identity_Card_Back.getCode())) {
                    queryVO.setLegalPersonIdentityCardBack(detail.getDetail());
                } else if (detail.getTagEnum().equals(MemberConfigTagEnum.Unified_Credit_Code.getCode())) {
                    queryVO.setUnifiedCreditCode(detail.getDetail());
                } else if (detail.getTagEnum().equals(MemberConfigTagEnum.Registered_capital.getCode())) {
                    queryVO.setRegisteredCapital(detail.getDetail());
                } else if (detail.getTagEnum().equals(MemberConfigTagEnum.Establishment_Date.getCode())) {
                    queryVO.setEstablishmentDate(detail.getDetail());
                } else if (detail.getTagEnum().equals(MemberConfigTagEnum.Business_Licence.getCode())) {
                    queryVO.setBusinessLicence(detail.getDetail());
                } else if (detail.getTagEnum().equals(MemberConfigTagEnum.Register_Area.getCode())) {
                    queryVO.setRegisterArea(detail.getDetail());
                    queryVO.setProvinceName(detail.getProvinceName());
                    queryVO.setCityName(detail.getCityName());
                } else if (detail.getTagEnum().equals(MemberConfigTagEnum.Register_Address.getCode())) {
                    queryVO.setRegisterAddress(detail.getDetail());
                }
            }
        }

        return Wrapper.success(queryVO);
    }


    /**
     * 修改平台会员注册资料
     *
     * @param platformRelation      平台会员关系
     * @param email                 邮箱
     * @param detail                前端传递的修改结果
     * @param updateEmail           是否检查并更新Email
     * @param forcePlatformValidate 是否强制平台审核，如果不强制，则根据注册资料配置判断
     * @return 修改结果
     */
    @Transactional(rollbackFor = BusinessException.class)
    @Override
    public Wrapper<Void> updatePlatformMemberRegisterDetail(MemberRelationDO platformRelation, String email, Map<String, Object> detail, boolean updateEmail, boolean forcePlatformValidate) {
        MemberDO memberDO = platformRelation.getSubMember();
        if (memberDO == null) {
            return Wrapper.fail(ResponseCode.MC_MS_MEMBER_DOES_NOT_EXIST);
        }

        MemberUserDO memberUserDO = memberUserRepository.findFirstByMemberAndTypeEnum(memberDO, MemberUserAuthTypeEnum.ADMIN.getCode());
        if (memberUserDO == null) {
            return Wrapper.fail(ResponseCode.MC_MS_MEMBER_USER_DOES_NOT_EXIST);
        }

        Set<MemberConfigDO> memberConfigSet = memberDO.getRoles().stream().flatMap(roleDO -> roleDO.getConfigs().stream()).collect(Collectors.toSet());
        List<MemberRegisterDetailDO> registerDetails = new ArrayList<>();
        Wrapper<String> checkResult = checkMemberRegisterDetail(detail, new ArrayList<>(memberConfigSet), registerDetails, memberDO.getName());
        if (checkResult.getCode() != ResponseCode.SUCCESS.getCode()) {
            return Wrapper.fail(checkResult.getCode(), checkResult.getMessage());
        }

        String memberName = checkResult.getData();
        //公司名称是否已被注册
        if (StringUtils.hasLength(memberName) && memberRepository.existsByNameAndIdNot(memberName, memberDO.getId())) {
            return Wrapper.fail(ResponseCode.MC_MS_MEMBER_NAME_REGISTERED);
        }

        //邮箱是否已被注册
        if (updateEmail && StringUtils.hasLength(email) && memberUserRepository.existsByRelTypeAndEmailAndIdNot(MemberRelationTypeEnum.OTHER.getCode(), email, memberUserDO.getId())) {
            return Wrapper.fail(ResponseCode.MC_MS_MEMBER_USER_EMAIL_EXISTS);
        }

        String registeredCapital = "", establishmentDate = "", businessLicence = "", registerArea = "", registerAddress = "";

        for (MemberRegisterDetailDO registerDetail : registerDetails) {
            registerDetail.setMember(memberDO);
            MemberConfigTagEnum tagEnum = MemberConfigTagEnum.parseCode(registerDetail.getMemberConfig().getTagEnum());
            if(tagEnum == null) {
                continue;
            }

            switch (tagEnum) {
                case Registered_capital:
                    registeredCapital = registerDetail.getDetail();
                    break;
                case Establishment_Date:
                    establishmentDate = registerDetail.getDetail();
                    break;
                case Business_Licence:
                    businessLicence = registerDetail.getDetail();
                    break;
                case Register_Area:
                    registerArea = registerDetail.getDetail();
                    break;
                case Register_Address:
                    registerAddress = registerDetail.getDetail();
                    break;
                default:
                    break;
            }
        }

        memberRegisterDetailRepository.saveAll(registerDetails);

        if (updateEmail) {
            memberDO.setEmail(StringUtils.hasLength(email) ? email : "");
            memberUserDO.setEmail(StringUtils.hasLength(email) ? email : "");
        }

        memberDO.setName(memberName);
        memberRepository.saveAndFlush(memberDO);

        memberUserDO.setName(memberName);
        memberUserRepository.saveAndFlush(memberUserDO);

        //提交平台审核
        if (forcePlatformValidate) {
            //自动提交审核
            Wrapper<WorkflowTaskResultBO> taskResult = workflowFeignService.startMemberProcess(platformRelation);
            if (taskResult.getCode() != ResponseCode.SUCCESS.getCode()) {
                TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();
                return Wrapper.fail(ResponseCode.MC_MS_MEMBER_VALIDATE_WORKFLOW_ERROR);
            }

            platformRelation.getValidateTask().setTaskId(taskResult.getData().getTaskId());
            platformRelation.setInnerStatus(taskResult.getData().getInnerStatus());
            platformRelation.setOuterStatus(MemberOuterStatusEnum.TO_PLATFORM_VERIFY.getCode());

            relationRepository.saveAndFlush(platformRelation);
        }

        //通知店铺模板服务，更改会员注册资料
        platformTemplateFeignService.notifyRegisterDetailChangedAsync(platformRelation.getSubMemberId(), platformRelation.getSubRoleId(), memberName, registeredCapital, establishmentDate, businessLicence, registerArea, registerAddress);

        return Wrapper.success();
    }

    /**
     * 查询用户注册资料
     *
     * @param userId 用户Id
     * @return 查询结果
     */
    @Override
    public Wrapper<UserDetailVO> getUserDetail(Long userId) {
        MemberUserDO memberUserDO = memberUserRepository.findById(userId).orElse(null);
        if (memberUserDO == null) {
            return Wrapper.fail(ResponseCode.MC_MS_MEMBER_USER_DOES_NOT_EXIST);
        }
        UserDetailVO detailVO = new UserDetailVO();
        detailVO.setUserId(memberUserDO.getId());
        detailVO.setUserName(memberUserDO.getName());
        detailVO.setCountryCode(memberUserDO.getCountryCode());
        detailVO.setPhone(memberUserDO.getPhone());
        detailVO.setIdCardNo(memberUserDO.getIdCardNo());
        return Wrapper.success(detailVO);
    }

    /**
     * 检查注册资料、入库资料
     *
     * @param configDO 会员注册资料
     * @param value    新增、修改后的值
     * @return 检查结果
     */
    @Override
    public Wrapper<DetailCheckBO> checkDetail(MemberConfigDO configDO, String value) {
        List<MemberDetailLabelBO> labels = new ArrayList<>();
        Integer tagEnum;
        String memberName = "", detail, provinceCode = "", provinceName = "", cityCode = "", cityName = "", districtCode = "", districtName = "";

        //先检查枚举类型
        if ("select".equals(configDO.getFieldType()) || "radio".equals(configDO.getFieldType()) || "checkbox".equals(configDO.getFieldType()) || "area".equals(configDO.getFieldType())) {
            //枚举类型不能为空
            if (!StringUtils.hasLength(value)) {
                return Wrapper.fail(ResponseCode.REQUEST_PARAM_CHECK_FAILED, MemberStringEnum.CHOOSE.getName() + configDO.getFieldLocalName());
            }
        }

        //省、市、区下拉框
        if ("area".equals(configDO.getFieldType())) {
            RegisterAreaVO area = SecurityStringUtils.deserializeObject(value, RegisterAreaVO.class);
            if (area == null) {
                return Wrapper.fail(ResponseCode.REQUEST_PARAM_CHECK_FAILED, "省市区下拉框参数格式不正确");
            }

            if (!StringUtils.hasLength(area.getProvinceCode()) || !area.getProvinceCode().endsWith("0000")) {
                return Wrapper.fail(ResponseCode.REQUEST_PARAM_CHECK_FAILED, "省编码格式错误");
            }

            if (!StringUtils.hasLength(area.getCityCode()) || !area.getCityCode().endsWith("00")) {
                return Wrapper.fail(ResponseCode.REQUEST_PARAM_CHECK_FAILED, "市编码格式错误");
            }

            if (!StringUtils.hasLength(area.getDistrictCode())) {
                return Wrapper.fail(ResponseCode.REQUEST_PARAM_CHECK_FAILED, "区编码格式错误");
            }

            List<String> codeList = Stream.of(area.getProvinceCode(), area.getCityCode(), area.getDistrictCode()).collect(Collectors.toList());
            List<String> prefixList = codeList.stream().map(code -> code.substring(0, 2)).collect(Collectors.toList());
            if (prefixList.stream().distinct().count() != 1) {
                return Wrapper.fail(ResponseCode.REQUEST_PARAM_CHECK_FAILED, "省、市、区编码不匹配");
            }

            List<CountryAreaDO> countryAreas = countryAreaRepository.findByCodeIn(codeList);
            if (CollectionUtils.isEmpty(countryAreas) || countryAreas.size() != 3) {
                return Wrapper.fail(ResponseCode.MC_MS_COUNTRY_AREA_DOES_NOT_EXIST);
            }

            provinceCode = area.getProvinceCode();
            cityCode = area.getCityCode();
            districtCode = area.getDistrictCode();
            for (CountryAreaDO countryArea : countryAreas) {
                if (countryArea.getCode().equals(provinceCode)) {
                    provinceName = countryArea.getName();
                } else if (countryArea.getCode().equals(cityCode)) {
                    cityName = countryArea.getName();
                } else {
                    districtName = countryArea.getName();
                }
            }

            detail = provinceName.concat(cityName).concat(districtName);
        } else if ("select".equals(configDO.getFieldType()) || "radio".equals(configDO.getFieldType())) {
            if(StringUtils.hasLength(value) && value.startsWith("[")) {
                return Wrapper.fail(ResponseCode.REQUEST_PARAM_CHECK_FAILED, configDO.getFieldLocalName() + "为单项选择，参数为整数类型");
            }

            Long labelId = SecurityStringUtils.convertStringToLong(value);
            if (NumberUtil.isNullOrZero(labelId)) {
                return Wrapper.fail(ResponseCode.REQUEST_PARAM_CHECK_FAILED, configDO.getFieldLocalName() + "标签不能为空");
            }

            MemberConfigLabelDO labelDO = configDO.getLabels().stream().filter(label -> label.getId().equals(labelId)).findFirst().orElse(null);
            if (labelDO == null) {
                return Wrapper.fail(ResponseCode.REQUEST_PARAM_CHECK_FAILED, configDO.getFieldLocalName().concat("标签不存在"));
            }

            labels = Stream.of(new MemberDetailLabelBO(labelDO.getId(), labelDO.getLabelValue())).collect(Collectors.toList());
            detail = labelDO.getLabelValue();
        } else if ("checkbox".equals(configDO.getFieldType())) {
            if(StringUtils.hasLength(value) && !value.startsWith("[")) {
                return Wrapper.fail(ResponseCode.REQUEST_PARAM_CHECK_FAILED, configDO.getFieldLocalName() + "为多项选择，参数为整数数组");
            }

            //其他枚举类型
            List<Long> labelIds = SecurityStringUtils.convertStringToLongList(value);
            if (CollectionUtils.isEmpty(labelIds)) {
                return Wrapper.fail(ResponseCode.REQUEST_PARAM_CHECK_FAILED, "标签列表不能为空");
            }

            if (labelIds.stream().anyMatch(labelId -> configDO.getLabels().stream().noneMatch(label -> label.getId().equals(labelId)))) {
                return Wrapper.fail(ResponseCode.REQUEST_PARAM_CHECK_FAILED, "标签不存在");
            }

            labels = configDO.getLabels().stream().filter(label -> labelIds.contains(label.getId())).map(label -> {
                MemberDetailLabelBO detailLabel = new MemberDetailLabelBO();
                detailLabel.setLabelId(label.getId());
                detailLabel.setLabelValue(label.getLabelValue());
                return detailLabel;
            }).collect(Collectors.toList());

            detail = configDO.getLabels().stream().filter(label -> labelIds.contains(label.getId())).sorted(Comparator.comparingInt(MemberConfigLabelDO::getLabelOrder)).map(MemberConfigLabelDO::getLabelValue).collect(Collectors.joining(","));
        } else {
            //检查是否为空
            if (configDO.getFieldEmpty().equals(EnableDisableStatus.DISABLE.getCode()) && !StringUtils.hasLength(value)) {
                return Wrapper.fail(ResponseCode.REQUEST_PARAM_CHECK_FAILED, MemberStringEnum.FILL_IN.getName() + configDO.getFieldLocalName());
            }

            //检查字段长度
            if (value != null && value.length() > configDO.getFieldLength()) {
                return Wrapper.fail(ResponseCode.REQUEST_PARAM_CHECK_FAILED, configDO.getFieldLocalName() + MemberStringEnum.EXCEED_LENGTH_LIMIT.getName());
            }

            //文件类型
            if(configDO.getFieldType().toLowerCase().equals(MemberConfigFieldTypeEnum.UPLOAD.getType())) {
                if(configDO.getFieldEmpty().equals(EnableDisableStatus.DISABLE.getCode()) && !StringUtils.hasLength(value)) {
                    return Wrapper.fail(ResponseCode.REQUEST_PARAM_CHECK_FAILED, MemberStringEnum.UPLOAD.getName() + configDO.getFieldLocalName());
                }

                if(StringUtils.hasLength(value) && !value.toLowerCase().startsWith("http://") && !value.toLowerCase().startsWith("https://")) {
                    return Wrapper.fail(ResponseCode.REQUEST_PARAM_CHECK_FAILED, configDO.getFieldLocalName() + " " + MemberStringEnum.URL_FORMAT_MISMATCH.getName());
                }
            }

            detail = StringUtils.hasLength(value) ? value : "";
        }

        tagEnum = configDO.getTagEnum() == null ? 0 : configDO.getTagEnum();
        if (tagEnum.equals(MemberConfigTagEnum.Member_Name.getCode())) {
            memberName = detail;
        }

        return Wrapper.success(new DetailCheckBO(tagEnum, memberName, detail, provinceCode, provinceName, cityCode, cityName, districtCode, districtName, labels));
    }

    /**
     * 检查注册资料、入库资料的字段是否齐全
     *
     * @param memberConfigList 注册资料列表
     * @param detailMap    前端传递的注册、入库资料
     * @return 检查结果
     */
    @Override
    public Wrapper<Void> checkDetailFields(List<MemberConfigDO> memberConfigList, Map<String, Object> detailMap) {
        if(CollectionUtils.isEmpty(memberConfigList)) {
            return Wrapper.success();
        }

        if(CollectionUtils.isEmpty(detailMap)) {
            return Wrapper.fail(ResponseCode.MC_MS_MEMBER_DEPOSITORY_DETAIL_IS_MISSING);
        }

        MemberConfigDO memberConfig = memberConfigList.stream().filter(config -> detailMap.keySet().stream().noneMatch(key -> key.equals(config.getFieldName()))).findFirst().orElse(null);
        if(memberConfig != null) {
            return Wrapper.fail(ResponseCode.MC_MS_MEMBER_DEPOSITORY_DETAIL_IS_MISSING, MemberStringEnum.FILL_IN.getName() + memberConfig.getFieldLocalName());
        }

        return Wrapper.success();
    }

    /**
     * 查询注册资料时，根据注册资料的FieldType，获取前端显示的值
     *
     * @param detailDO 注册资料
     * @return 字段值
     */
    private DetailValueBO getDetailValue(MemberRegisterDetailDO detailDO) {
        DetailValueBO detail = new DetailValueBO();
        //省、市、区下拉框
        if ("area".equals(detailDO.getFieldType())) {
            detail.setFieldValue(new RegisterAreaVO(detailDO.getProvinceCode(), detailDO.getCityCode(), detailDO.getDistrictCode()));
            detail.setLastValue(new RegisterAreaVO());
        } else if ("select".equals(detailDO.getFieldType()) || "radio".equals(detailDO.getFieldType())) {
            MemberDetailLabelBO labelBO = detailDO.getLabels().stream().findFirst().orElse(null);
            detail.setFieldValue(labelBO == null ? null : labelBO.getLabelId());
            detail.setLastValue(null);
        } else if ("checkbox".equals(detailDO.getFieldType())) {
            detail.setFieldValue(detailDO.getLabels().stream().map(MemberDetailLabelBO::getLabelId).collect(Collectors.toList()));
            detail.setLastValue(new ArrayList<>());
        } else {
            detail.setFieldValue(detailDO.getDetail());
            detail.setLastValue("");
        }

        return detail;
    }

    /**
     * 查询注册资料时，根据注册资料的FieldType，获取前端显示的值
     *
     * @param detailDO 注册资料
     * @return 字段值
     */
    private Object getSingleDetailValue(MemberRegisterDetailDO detailDO) {
        //省、市、区下拉框
        if ("area".equals(detailDO.getFieldType())) {
            return new RegisterAreaVO(detailDO.getProvinceCode(), detailDO.getCityCode(), detailDO.getDistrictCode());
        } else if ("select".equals(detailDO.getFieldType()) || "radio".equals(detailDO.getFieldType())) {
            MemberDetailLabelBO labelBO = detailDO.getLabels().stream().findFirst().orElse(null);
            if(labelBO != null) {
                return labelBO.getLabelId();
            } else {
                return null;
            }
        } else if ("checkbox".equals(detailDO.getFieldType())) {
            return detailDO.getLabels().stream().map(MemberDetailLabelBO::getLabelId).collect(Collectors.toList());
        } else {
            return detailDO.getDetail();
        }
    }
}
